package studiodiva.portfolio.client.model;

import static studiodiva.portfolio.client.lib.lang.Lang.equal;
import static studiodiva.portfolio.client.lib.lang.Lang.no;

import studiodiva.portfolio.client.lib.even.EventFunction;
import studiodiva.portfolio.client.lib.history.HistoryItem;
import studiodiva.portfolio.client.lib.history.HistoryItems;
import studiodiva.portfolio.client.lib.lang.Base;
import studiodiva.portfolio.client.model.titles.Page;
import studiodiva.portfolio.client.model.titles.Title;
import studiodiva.portfolio.client.model.titles.Titles;
import studiodiva.portfolio.client.model.titles.Titles.TitleType;

public class PageHistory extends Base {

  private static String DEFAULT_PAGE = "none";
  private final HistoryItems items = new HistoryItems();
  private final HistoryItem pageItem = items.create("page", DEFAULT_PAGE);

  public PageHistory(HasApplication hasApplication) {
    initialize(hasApplication);
    items.initialize(this);
  }

  public void initialize() {
    register(pageItem, HistoryItem.ON_CHANGE, new EventFunction<String>() {
      public void run(String value) {
        loadFromPageHistoryItem(value);
      }
    });
    register(getApplication().getTitles(), Titles.ON_CHANGE, new EventFunction<Title>() {
      public void run(Title value) {
        onTitleChange(value);
      }
    });
    loadFromPageHistoryItem(pageItem.getValue());
  }

  private void loadFromPageHistoryItem(String pageid) {
    for (Title title : getApplication().getTitles())
      for (Page page : title)
        if (equal(pageid, page.getId())) {
          title.showPage(pageid);
          getApplication().getTitles().open(title.getType());
          return;
        }
    getApplication().getTitles().open(TitleType.closed);
  }

  private void onTitleChange(Title title) {
    if (no(title)) {
      pageItem.save(DEFAULT_PAGE);
      unRegisterByEvent(Title.ON_PAGE_CHANGE);
    } else {
      pageItem.save(title.getPage().getId());
      registerReplaceByEvent(title, Title.ON_PAGE_CHANGE, new EventFunction<Page>() {
        public void run(Page value) {
          pageItem.save(value.getId());
        }
      });
    }
  }
}
